package cn.tedu.project.oa.management.service;

import cn.tedu.project.oa.attendanceRule.mapper.OvertimeRuleMapper;
import cn.tedu.project.oa.attendanceRule.mapper.WorkingShiftMapper;
import cn.tedu.project.oa.attendanceRule.pojo.entity.OvertimeRule;
import cn.tedu.project.oa.attendanceRule.pojo.entity.WorkingShift;
import cn.tedu.project.oa.attendanceRule.pojo.param.WorkingShiftSelectParam;
import cn.tedu.project.oa.attendanceRule.pojo.vo.WorkingShiftVO;
import cn.tedu.project.oa.attendanceRule.service.IWorkingShiftService;
import cn.tedu.project.oa.dingding.DingDingService;
import cn.tedu.project.oa.management.mapper.ManagementMapper;
import cn.tedu.project.oa.management.mapper.ManagementUserMapper;
import cn.tedu.project.oa.management.pojo.dto.*;
import cn.tedu.project.oa.management.pojo.entity.Management;
import cn.tedu.project.oa.management.pojo.entity.ManagementUser;
import cn.tedu.project.oa.management.pojo.vo.ManagementInfoVO;
import cn.tedu.project.oa.management.pojo.vo.ManagementVO;
import cn.tedu.project.oa.sys.user.mapper.UserMapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.taobao.api.ApiException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
@Slf4j
public class ManagementServiceImpl implements ManagementService{
    @Autowired
    private ManagementMapper managementMapper;
    @Autowired
    private OvertimeRuleMapper overtimeRuleMapper;
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private ManagementUserMapper managementUserMapper;
    @Autowired
    private IWorkingShiftService workingShiftService;

    /**
     * 查询考勤管理
     *
     * @param id 考勤管理主键
     * @return 考勤管理
     */
    @Override
    public ManagementInfoVO selectManagementById(Long id) {
        Management management = managementMapper.selectById(id);
        ManagementInfoVO managementInfoVO = new ManagementInfoVO();
        BeanUtils.copyProperties(management,managementInfoVO);
        WorkingShiftSelectParam workingShiftSelectParam = new WorkingShiftSelectParam();
        WorkingShiftVO workingShiftVO;
        QueryWrapper<ManagementUser> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("attendance_management_id", id);
        List<ManagementUser> managementUsers = managementUserMapper.selectList(queryWrapper);
        List<Long> userIdList = null;
        userIdList = managementUsers.stream().map(ManagementUser::getUserId).collect(Collectors.toList());
        managementInfoVO.setUserList(userIdList);
        Long sunWorkingShiftId = management.getSunWorkingShiftId();
        if (sunWorkingShiftId != 0){
            workingShiftSelectParam.setId(sunWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setSunWorkingShift(workingShiftVO);
        }
        Long monWorkingShiftId = management.getMonWorkingShiftId();
        if (monWorkingShiftId != 0){
            workingShiftSelectParam.setId(monWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setMonWorkingShift(workingShiftVO);
        }
        Long tueWorkingShiftId = management.getTueWorkingShiftId();
        if (tueWorkingShiftId != 0){
            workingShiftSelectParam.setId(tueWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setTueWorkingShift(workingShiftVO);
        }
        Long wedWorkingShiftId = management.getWedWorkingShiftId();
        if (wedWorkingShiftId != 0){
            workingShiftSelectParam.setId(wedWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setWedWorkingShift(workingShiftVO);
        }
        Long thuWorkingShiftId = management.getThuWorkingShiftId();
        if (thuWorkingShiftId != 0){
            workingShiftSelectParam.setId(thuWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setThuWorkingShift(workingShiftVO);
        }
        Long friWorkingShiftId = management.getFriWorkingShiftId();
        if (friWorkingShiftId != 0){
            workingShiftSelectParam.setId(friWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setFriWorkingShift(workingShiftVO);
        }
        Long satWorkingShiftId = management.getSatWorkingShiftId();
        if (satWorkingShiftId != 0){
            workingShiftSelectParam.setId(satWorkingShiftId);
            workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
            managementInfoVO.setSatWorkingShift(workingShiftVO);
        }
        return managementInfoVO;
    }

    /**
     * 查询考勤管理列表
     *
     * @return 考勤管理
     */
    @Override
    public List<ManagementVO> selectManagementList(ManagementGetListQuery managementGetListQuery) {
        QueryWrapper<Management> queryWrapper = new QueryWrapper<>();
        if (managementGetListQuery.getName() != null){
            queryWrapper.like("name",managementGetListQuery.getName());
        }

        List<Management> managementList = managementMapper.selectList(queryWrapper);
        List<ManagementVO> managementVOList = new ArrayList<>();
        WorkingShiftSelectParam workingShiftSelectParam = new WorkingShiftSelectParam();
        WorkingShiftVO workingShiftVO;
        for (Management management : managementList){
            ManagementVO managementVO = new ManagementVO();
            managementVO.setName(management.getName());
            managementVO.setId(management.getId());
            Long sunWorkingShiftId = management.getSunWorkingShiftId();
            if (sunWorkingShiftId != 0){
                workingShiftSelectParam.setId(sunWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setSunWorkingShift(workingShiftVO);
            }
            Long monWorkingShiftId = management.getMonWorkingShiftId();
            if (monWorkingShiftId != 0){
                workingShiftSelectParam.setId(monWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setMonWorkingShift(workingShiftVO);
            }
            Long tueWorkingShiftId = management.getTueWorkingShiftId();
            if (tueWorkingShiftId != 0){
                workingShiftSelectParam.setId(tueWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setTueWorkingShift(workingShiftVO);
            }
            Long wedWorkingShiftId = management.getWedWorkingShiftId();
            if (wedWorkingShiftId != 0){
                workingShiftSelectParam.setId(wedWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setWedWorkingShift(workingShiftVO);
            }
            Long thuWorkingShiftId = management.getThuWorkingShiftId();
            if (thuWorkingShiftId != 0){
                workingShiftSelectParam.setId(thuWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setThuWorkingShift(workingShiftVO);
            }
            Long friWorkingShiftId = management.getFriWorkingShiftId();
            if (friWorkingShiftId != 0){
                workingShiftSelectParam.setId(friWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setFriWorkingShift(workingShiftVO);
            }
            Long satWorkingShiftId = management.getSatWorkingShiftId();
            if (satWorkingShiftId != 0){
                workingShiftSelectParam.setId(satWorkingShiftId);
                workingShiftVO = workingShiftService.selectWorkingShiftList(workingShiftSelectParam).get(0);
                managementVO.setSatWorkingShift(workingShiftVO);
            }
            managementVOList.add(managementVO);
        }
        return managementVOList;
    }


    //新建考勤管理
    @Override
    public int insertManagement(ManagementAddParam managementAddParam) {
        Management management = new Management();
        ManagementUser managementUser = new ManagementUser();
        BeanUtils.copyProperties(managementAddParam,management);

        //通过oa用户id获取钉钉用户id
        List<String> dingDingUserIdList = getDingDingUserIdByOaUserId(managementAddParam.getUserList());

        //设置钉钉入参
        log.debug("钉钉用户id集合："+dingDingUserIdList);
        DingDingManagementAddParam dingDingManagementAddParam = new DingDingManagementAddParam();
        BeanUtils.copyProperties(managementAddParam, dingDingManagementAddParam);
        dingDingManagementAddParam.setUserList(dingDingUserIdList);
        try {
            Long id = DingDingService.addManagement(dingDingManagementAddParam);
            management.setId(id);
            managementUser.setAttendanceManagementId(id);
        } catch (ApiException e) {
            throw new RuntimeException(e);
        }

        //关联用户和考勤管理
        for (Long id : managementAddParam.getUserList()){
            managementUser.setUserId(id);
            managementUserMapper.insert(managementUser);
        }

        //设置每日班次
        management.setSunWorkingShiftId(managementAddParam.getWorkingClassList().get(0));
        management.setMonWorkingShiftId(managementAddParam.getWorkingClassList().get(1));
        management.setTueWorkingShiftId(managementAddParam.getWorkingClassList().get(2));
        management.setWedWorkingShiftId(managementAddParam.getWorkingClassList().get(3));
        management.setThuWorkingShiftId(managementAddParam.getWorkingClassList().get(4));
        management.setFriWorkingShiftId(managementAddParam.getWorkingClassList().get(5));
        management.setSatWorkingShiftId(managementAddParam.getWorkingClassList().get(6));
        management.setCreateTime(new Date());
        return managementMapper.insert(management);
    }

    /**
     * 修改考勤管理
     *
     * @return 结果
     */
    @Override
    public int updateManagement(ManagementAddParam managementAddParam) {
        Management management = new Management();
        BeanUtils.copyProperties(managementAddParam,management);
        management.setUpdateTime(new Date());
        return managementMapper.updateManagement(management);
    }



    /**
     * 删除考勤管理信息
     *
     * @param id 考勤管理主键
     * @return 结果
     */
    @Override
    public int deleteManagementById(Long id) {
        try {
            DingDingService.deleteManagementById(id);
        } catch (ApiException e) {
            throw new RuntimeException(e);
        }
        return managementMapper.deleteById(id);
    }

    //更新参与考勤人员
    @Override
    public void updateMember(MemberUpdateParam memberUpdateParam) {
        //更新钉钉参数
        DingDingMemberUpdateParam dingDingMemberUpdateParam = new DingDingMemberUpdateParam();
        //通过oa用户id获取钉钉用户id
        List<String> addUserList = getDingDingUserIdByOaUserId(memberUpdateParam.getAddUserList());
        List<String> removeUserList = getDingDingUserIdByOaUserId(memberUpdateParam.getRemoveUserList());
        dingDingMemberUpdateParam.setAddUserList(addUserList);
        dingDingMemberUpdateParam.setRemoveUserList(removeUserList);
        dingDingMemberUpdateParam.setId(memberUpdateParam.getId());
        boolean success;
        try {
            log.debug("钉钉入参："+dingDingMemberUpdateParam);
            success = DingDingService.updateMember(dingDingMemberUpdateParam);
        } catch (ApiException e) {
            throw new RuntimeException(e);
        }

        if (success){
            //更新oa参数
            ManagementUser managementUser = new ManagementUser();
            managementUser.setAttendanceManagementId(memberUpdateParam.getId());
            if (!memberUpdateParam.getAddUserList().isEmpty()){
                for (Long userId : memberUpdateParam.getAddUserList()){
                    managementUser.setUserId(userId);
                    managementUserMapper.insert(managementUser);
                }
            }
            if (!memberUpdateParam.getRemoveUserList().isEmpty()){
                QueryWrapper<ManagementUser> queryWrapper = new QueryWrapper<>();
                queryWrapper.eq("attendance_management_id", memberUpdateParam.getId());
                for (Long userId : memberUpdateParam.getRemoveUserList()){
                    queryWrapper.eq("user_id", userId);
                    managementUserMapper.delete(queryWrapper);
                }
            }
        }
    }

    //通过oa用户id获取钉钉用户id
    public List<String> getDingDingUserIdByOaUserId(List<Long> userIdList){
        //通过oa用户id获取手机号
        List<String> mobileList = new ArrayList<>();
        for (Long id : userIdList){
            String mobile = userMapper.selectUserById(id).getPhone();
            mobileList.add(mobile);
        }

        //通过手机号获取钉钉用户id
        List<String> dingDingUserIdList = new ArrayList<>();
        for (String mobile : mobileList){
            try {
                String dingDingUserId = DingDingService.getUserIdByMobile(mobile);
                dingDingUserIdList.add(dingDingUserId);
            } catch (ApiException e) {
                throw new RuntimeException(e);
            }
        }
        return dingDingUserIdList;
    }

}
